package com.gmics.unifiq;

import java.io.IOException;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.List;

import org.json.JSONObject;

import android.content.Intent;
import android.graphics.Color;
import android.location.Address;
import android.location.Geocoder;
import android.os.AsyncTask;
import android.os.Bundle;
import android.support.v4.app.FragmentActivity;
import android.widget.ImageView;
import android.widget.TextView;
import android.widget.Toast;

import com.gmics.android.R;
import com.gmics.unifiq.controller.DirectionsJSONParser;
import com.google.android.gms.maps.CameraUpdate;
import com.google.android.gms.maps.CameraUpdateFactory;
import com.google.android.gms.maps.GoogleMap;
import com.google.android.gms.maps.SupportMapFragment;
import com.google.android.gms.maps.model.BitmapDescriptorFactory;
import com.google.android.gms.maps.model.LatLng;
import com.google.android.gms.maps.model.LatLngBounds;
import com.google.android.gms.maps.model.MarkerOptions;
import com.google.android.gms.maps.model.PolylineOptions;

public class ComparisonMap extends FragmentActivity {

	/** A class to parse the Google Places in JSON format */
    private class ParserTask extends AsyncTask<String, Integer, List<List<HashMap<String,String>>> >
    {
 
        // Parsing the data in non-ui thread
        @Override
        protected List<List<HashMap<String, String>>> doInBackground(String... jsonData) {
 
            JSONObject jObject;
            List<List<HashMap<String, String>>> routes = null;
 
            try{
                jObject = new JSONObject(jsonData[0]);
                DirectionsJSONParser parser = new DirectionsJSONParser();
 
                // Starts parsing data
                routes = parser.parse(jObject);
            }catch(Exception e){
                e.printStackTrace();
            }
            return routes;
        }
 
        // Executes in UI thread, after the parsing process
        @Override
        protected void onPostExecute(List<List<HashMap<String, String>>> result) 
        {
            ArrayList<LatLng> points = null;
            PolylineOptions lineOptions = null;
            String distance = "";
            String duration = "";
 
            if(result.size()<1){
                Toast.makeText(getBaseContext(), "No Points", Toast.LENGTH_SHORT).show();
                return;
            }
 
            // Traversing through all the routes
            for(int i=0;i<result.size();i++)
            {
                points = new ArrayList<LatLng>();
                lineOptions = new PolylineOptions();
 
                // Fetching i-th route
                List<HashMap<String, String>> path = result.get(i);
 
                // Fetching all the points in i-th route
                for(int j=0;j<path.size();j++){
                    HashMap<String,String> point = path.get(j);
 
                    if(j==0){    // Get distance from the list
                        distance = point.get("distance");
                        continue;
                    }else if(j==1){ // Get duration from the list
                        duration = point.get("duration");
                        continue;
                    }
 
                    double lat = Double.parseDouble(point.get("lat"));
                    double lng = Double.parseDouble(point.get("lng"));
                    LatLng position = new LatLng(lat, lng);
 
                    points.add(position);
                }
 
                // Adding all the points in the route to LineOptions
                lineOptions.addAll(points);
                lineOptions.width(2);
                lineOptions.color(Color.RED);
            }
 
            
            distanceTv.setText("Distance: " + distance);
            durationTv.setText("Duration: " + duration);
 
            // Drawing polyline in the Google Map for the i-th route
            map.addPolyline(lineOptions);      
        }
    }
	GoogleMap map;
	TextView distanceTv;
	TextView durationTv;
	TextView schoolTv, startTv, destTv;
	TextView startDescTv, destDescTv;
	
	double startLat=0, startLon=0, destLat=0, destLon=0;
	
	LatLng start, dest;

	@Override
	protected void onCreate(Bundle savedInstanceState) {
		// TODO Auto-generated method stub
		super.onCreate(savedInstanceState);
		setContentView(R.layout.comparison_map);
		
		
		ImageView img1 = (ImageView) findViewById(R.id.img1);
		ImageView img2 = (ImageView) findViewById(R.id.img2);
		
		
        distanceTv = (TextView) findViewById(R.id.tv_distance);
        durationTv = (TextView) findViewById(R.id.tv_time);
        startTv = (TextView) findViewById(R.id.tv_start);
        destTv = (TextView) findViewById(R.id.tv_dest);
        startDescTv = (TextView) findViewById(R.id.tv_startDesc);
        destDescTv = (TextView) findViewById(R.id.tv_destDesc);
        
        SupportMapFragment fm = (SupportMapFragment)getSupportFragmentManager().findFragmentById(R.id.map);
        map = fm.getMap();
        
        map.setMyLocationEnabled(true);
        
        Intent i = getIntent();
        
       	String mapData = i.getStringExtra("mapData");
       	
       	startLat = i.getDoubleExtra("startLat", 0);
       	startLon = i.getDoubleExtra("startLon", 0);
       	destLat = i.getDoubleExtra("destLat", 0);
       	destLon = i.getDoubleExtra("destLon", 0);
       	
       	start = new LatLng(startLat,startLon);
       	dest = new LatLng(destLat,destLon);
        
       	showPoints();
       	
       	
        ParserTask parserTask = new ParserTask();
        
        // Invokes the thread for parsing the JSON data
        parserTask.execute(mapData);
     
        //set TextViews
       	setTextViews(i);
	}
	
	private void setTextViews(Intent i)
	{
		// Set Start Address
        String startAddress = i.getStringExtra("startAddress");
		Geocoder geocoder = new Geocoder(getApplicationContext());  
		List<Address> addresses = null;
		String startDesc = null;
		try {
			if (startAddress.equals("usecurrentlocation"))
			{
				addresses = geocoder.getFromLocation(startLat, startLon, 1);
				startDesc = "Current Location";
			}
			else
			{
				addresses = geocoder.getFromLocationName(startAddress, 1);
				startDesc = "Home";
			}
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

		if(addresses.size() > 0) {
		    startAddress = addresses.get(0).getAddressLine(0);
		    startDescTv.setText(startDesc);
		    startTv.setText(startAddress);
		}
        
		// Set Dest Address
		geocoder = new Geocoder(getApplicationContext());  
		addresses = null;
		try {
				addresses = geocoder.getFromLocation(destLat, destLon, 1);
			
		} catch (IOException e) {
			// TODO Auto-generated catch block
			e.printStackTrace();
		}

		if(addresses.size() > 0) {
		    String destAddress = addresses.get(0).getAddressLine(0);
		    destDescTv.setText(i.getStringExtra("uniName") + ", " + i.getStringExtra("schoolName"));
		    destTv.setText(destAddress);
		}
		
	}
	
    private void showPoints()
	{	
		ArrayList<LatLng> markerPoints = new ArrayList<LatLng>();
        // Display directions from Start to Location
        MarkerOptions options = new MarkerOptions();
        
        options.position(start);
        options.icon(BitmapDescriptorFactory.fromResource(R.drawable.greenpin));
        map.addMarker(options);
        markerPoints.add(start);
        
        
        options.position(dest);
        options.icon(BitmapDescriptorFactory.fromResource(R.drawable.bluepin));
        map.addMarker(options);
        markerPoints.add(dest);
        
        
        // Set Camera Position
        LatLngBounds.Builder builder = new LatLngBounds.Builder();
        
        for (int i=0; i<markerPoints.size(); i++){
        	builder.include(markerPoints.get(i));
        }
        
        LatLngBounds bounds = builder.build();
        
        int padding = 0; // offset from edges of the map in pixels
        CameraUpdate cu = CameraUpdateFactory.newLatLngBounds(bounds, 500, 500 , padding);
        map.moveCamera(cu);
		
	}



}
